
#include "apdu_lib_digest_mgr.h"
#include "apdu_lib_common.h"

#include "../apdu.core/apdu.h"

#include "../../mk_lib/mk_auto_ptr.h"
#include "../../mk_lib/mk_utility.h"

#include <stdlib.h>
#include <string.h>
#include "../apdu.algo/mac.h"

extern int	g_sw;

int app_digest_init(HANDLE devHandle, int hash_algo, unsigned char * sm2_pub_key_blob, int pub_key_blob_len, 
					unsigned char * user_id, int id_len, int display )
{
	apdu * newApdu  =  NULL;
	newApdu = get_digest_mgr()->create_apdu_digest_init(hash_algo, sm2_pub_key_blob, pub_key_blob_len,
							user_id, id_len, display);

	mk_auto_ptr<apdu> ap(newApdu);

	if( 0 != get_dev_mgr()->transmit_apdu(devHandle,newApdu, &g_sw))
	{
		return 1;
	}

	if(g_sw != 0x9000)
	{
		return 2;
	}

	return 0;

}

int app_digest( HANDLE devHandle, unsigned char * input, int input_len, unsigned char * hash_val, int * hash_len )
{
	apdu * newApdu  =  NULL;
	newApdu = get_digest_mgr()->create_apdu_digest(input, input_len);

	mk_auto_ptr<apdu> ap(newApdu);

	if( 0 != get_dev_mgr()->transmit_apdu(devHandle,newApdu, &g_sw))
	{
		return 1;
	}

	if(g_sw != 0x9000)
	{
		return 2;
	}

	int data_len = 0;
	unsigned char * data = newApdu->get_response_data(&data_len);
	if(*hash_len < data_len)
	{
		return 3;
	}
	*hash_len = data_len;
	memcpy(hash_val, data, data_len);
	return 0;
}

int app_digest_update( HANDLE devHandle, unsigned char * input, int input_len, int display )
{
	apdu * newApdu  =  NULL;
	newApdu = get_digest_mgr()->create_apdu_digest_update(input, input_len, display);

	mk_auto_ptr<apdu> ap(newApdu);

	if( 0 != get_dev_mgr()->transmit_apdu(devHandle,newApdu, &g_sw))
	{
		return 1;
	}

	if(g_sw != 0x9000)
	{
		return 2;
	}

	return 0;
}

int app_digest_file(HANDLE devHandle, int app_id, char * file_name, int offset, int read_len)
{
	apdu * newApdu  =  NULL;
	newApdu = get_digest_mgr()->create_apdu_digest_file(app_id, offset, read_len, file_name);

	mk_auto_ptr<apdu> ap(newApdu);

	if( 0 != get_dev_mgr()->transmit_apdu(devHandle,newApdu, &g_sw))
	{
		return 1;
	}

	if(g_sw != 0x9000)
	{
		return 2;
	}

	return 0;
}


int app_digest_final( HANDLE devHandle, unsigned char * input, int input_len, 
					 unsigned char * hash_val, int * hash_len )
{
	apdu * newApdu  =  NULL;
	newApdu = get_digest_mgr()->create_apdu_digest_final(input, input_len);

	mk_auto_ptr<apdu> ap(newApdu);

	if( 0 != get_dev_mgr()->transmit_apdu(devHandle,newApdu, &g_sw))
	{
		return 1;
	}

	if(g_sw != 0x9000)
	{
		return 2;
	}

	int data_len = 0;
	unsigned char * data = newApdu->get_response_data(&data_len);
	if(*hash_len < data_len)
	{
		return 3;
	}
	*hash_len = data_len;
	memcpy(hash_val, data, data_len);
	return 0;
}
